/**
 * fshows.com
 * Copyright (C) 2013-2020 All Rights Reserved.
 */
package com.fshows.leshuapay.sdk.client.impl;

import cn.hutool.core.util.StrUtil;
import cn.hutool.http.HttpUtil;
import com.alibaba.fastjson.JSON;
import com.fshows.leshuapay.sdk.client.UploadAttachClient;
import com.fshows.leshuapay.sdk.exception.LeshuaException;
import com.fshows.leshuapay.sdk.request.UploadAttachRequest;
import com.fshows.leshuapay.sdk.response.LeshuaBaseResponse;
import com.fshows.leshuapay.sdk.response.UploadAttachResponse;
import com.fshows.leshuapay.sdk.util.BrushMD5;
import com.fshows.leshuapay.sdk.util.DateUtil;
import com.fshows.leshuapay.sdk.util.FsHttpUtil;
import com.fshows.leshuapay.sdk.util.ReqSerialNoUtil;
import com.fshows.leshuapay.sdk.util.SignUtil;
import com.fshows.leshuapay.sdk.util.StringPool;
import com.google.common.collect.Maps;
import lombok.Data;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.codec.binary.Base64;
import org.apache.commons.codec.digest.DigestUtils;
import org.apache.commons.io.FileUtils;
import org.apache.commons.lang3.RandomStringUtils;
import org.apache.commons.lang3.SystemUtils;
import org.apache.commons.lang3.exception.ExceptionUtils;

import java.io.File;
import java.io.UnsupportedEncodingException;
import java.net.URI;
import java.util.Map;


/**
 * @author zhaoyi
 * @version LeshuaMerchantGateWayClientImpl.java, v 0.1 2020-07-23 11:40 AM zhaoyi
 */
@Slf4j
@Data
public class UploadAttachClientImpl implements UploadAttachClient {

    /**
     * 图片文件上传的临时目录
     */
    public static final String IMG_FILE_SAVE_TEMP_DIR = SystemUtils.getUserHome() +
            File.separator + "files" +
            File.separator + "upload" +
            File.separator + "leshua" +
            File.separator + "temp" +
            File.separator;
    /**
     * 乐刷成功标识
     */
    private static final String SUCCESS = "000000";
    /**
     * 请求地址
     */
    private String serverUrl;
    /**
     * 服务商id
     */
    private String agentId;
    /**
     * 服务商私钥
     */
    private String privateKey;

    public UploadAttachClientImpl(String serverUrl, String agentId, String privateKey) {
        this.serverUrl = serverUrl;
        this.agentId = agentId;
        this.privateKey = privateKey;
    }

    @Override
    public UploadAttachResponse upload(String filePath, String subAgentId) throws Exception {
        return this.upload(serverUrl, StrUtil.blankToDefault(subAgentId, agentId), privateKey, filePath);
    }

    /**
     * 乐刷图片上传
     *
     * @param serverUrl
     * @param agentId
     * @param privateKey
     * @param filePath
     * @return {"photoUrl":"picture/M00/02/75/rBQhy1-ZFk-AS8hPAAK-UaBP240502.png"}
     * 需要再转一次json后取出
     * @throws LeshuaException
     */
    @Override
    public UploadAttachResponse upload(String serverUrl, String agentId, String privateKey, String filePath) throws Exception {
        if (filePath == null) {
            throw new IllegalArgumentException("文件路径不能为空");
        }
        UploadAttachResponse response = new UploadAttachResponse();
        //下载图片至本地
        String localFilePath = downloadFile(filePath);
        if (StringPool.EMPTY.equals(localFilePath)) {
            log.error("附件图片下载失败,filePath={}", filePath);
            return response;
        }
        File file = new File(localFilePath);
        String fileMD5 = DigestUtils.md5Hex(FileUtils.readFileToByteArray(file));
        UploadAttachRequest request = new UploadAttachRequest();
        request.setFileMD5(fileMD5);
        Map<String, String> requestMap = Maps.newHashMap();
        getRequestMap(requestMap, privateKey, request, agentId);
        String reqSerialNo = requestMap.get("reqSerialNo");
        log.info("乐刷商户附件图片上传接口请求乐刷入参 >> upload >> url={}, params={}, reqSerialNo={}, filePath={}", serverUrl, request, reqSerialNo, filePath);
        long startTime = System.currentTimeMillis();
        //上传本地路径文件
        File uploadFile = new File(localFilePath);
        String result = FsHttpUtil.postMedia(serverUrl, requestMap, uploadFile, 0);
        log.info("乐刷商户附件图片上传接口请求乐刷出参 >> upload >> url={}, params={}, result={}, runTimes={}", serverUrl, request, result, System.currentTimeMillis() - startTime);
        if (result == null) {
            return response;
        }
        LeshuaBaseResponse baseResponse = JSON.parseObject(result, LeshuaBaseResponse.class);
        if (baseResponse != null && SUCCESS.equals(baseResponse.getRespCode()) && baseResponse.getData() != null) {
            response.setPhotoUrl(JSON.parseObject(baseResponse.getData().toString()).getString("photoUrl"));
        }
        //删除本地文件
        if (file.exists()) {
            file.delete();
        }
        return response;
    }

    /**
     * 乐刷调用核心接口
     *
     * @param requestMap
     * @param privateKey
     * @param request
     * @param agentId
     * @throws Exception
     */
    public void getRequestMap(Map<String, String> requestMap, String privateKey, UploadAttachRequest request, String agentId) throws LeshuaException {
        //加签
        String waitSign = SignUtil.SING_PREFIX + privateKey + JSON.toJSONString(request);
        try {
            String sign = Base64.encodeBase64String(BrushMD5.md5(waitSign).getBytes(SignUtil.DEFAULT_CHARSET));
            requestMap.put("agentId", agentId);
            requestMap.put("version", SignUtil.DEFAULT_VERSION);
            requestMap.put("reqSerialNo", ReqSerialNoUtil.getReqSerialNo());
            requestMap.put("sign", sign);
            requestMap.put("data", JSON.toJSONString(request));
        } catch (UnsupportedEncodingException e) {
            log.info("签名异常,e={}", ExceptionUtils.getStackTrace(e));
            throw new LeshuaException("签名异常", e);
        }
    }

    private String downloadFile(String picPath) throws Exception {
        //文件保存的地址
        String savePath = IMG_FILE_SAVE_TEMP_DIR + DateUtil.getNowDateStr();
        //String substring = ReUtil.delAll("\\?.*", picPath.substring(picPath.lastIndexOf(".")));
        String filePath = (new URI(picPath)).getPath();
        String substring = filePath.substring(filePath.lastIndexOf(".") - 1);
        //重新生成的文件名 不包括文件类型
        String fileName = RandomStringUtils.randomAlphanumeric(10) + substring;
        //将文件下载到本地指定文件夹
//        fileName = FileUtil.downLoadFromUrlNew(picPath, fileName, savePath);
        final String targetFilePath = savePath + File.separator + fileName;
        log.info("UploadAttachClientImpl >> downloadFile,targetFilePath={}", targetFilePath);
        HttpUtil.downloadFile(picPath, targetFilePath);
        if (StringPool.EMPTY.equals(fileName)) {
            return StringPool.EMPTY;
        }
        return targetFilePath;
    }
}
